#define _CRT_SECURE_NO_WARNINGS

#include <stdio.h>
#include "strlib.h"
#include "genlib.h"
#include "simpio.h"

/*Private procedures*/
static void printGrayCode(int nBits);
static void generateGrayCode(int nBits, string str, bool reverse);
static void printGroupMembers();

/*Main function*/
main(){

	printGroupMembers();

	int nBits;

	printf("Gray Code Bit Generator - (-1 to quit)\n\n");

	while (TRUE){
		
		printf("\nInput number of bits: ");
		nBits = GetInteger();

		if (nBits == -1){
			break;
		}

		printf("\n%d-bit string\n\n", nBits);

		printGrayCode(nBits);
	}
}

/*
* Procedure: printGroupMembers
* Usage: printGroupMembers();
* --------------------------------
* This procedure prints the authors of this 
* program to screen.
*/
static void printGroupMembers(){

	printf("This program was developed by: ");
	printf("Jim Glansk, S141587, ");
	printf("Henrik Wistbacka, S142066\n");
}

/*
* Procedure: printGrayCode
* Usage: printGrayCode(nBits);
* --------------------------------
* This procedure is a wrapper procedure
* to generate all Gray Code for up to and
* including the number of nBits. It prints
* the result to screen.
*/
static void printGrayCode(int nBits){

	generateGrayCode(nBits, "", FALSE);

}

/*
* Procedure: generateGrayCode
* Usage: generateGrayCode(nBits, str, reverse);
* --------------------------------
* This procedure generates all Gray Code up to 
* and including the number of nBits. Input is a
* string str, where the result is stored between calls.
* str is empty after all Gray Code is printed.
* reverse must be set to FALSE from start. 
*/
static void generateGrayCode(int nBits, string str, bool reverse){

	if (nBits == 0){
		printf("%s\n", str);
	}
	else{
		generateGrayCode(nBits - 1, Concat(str, reverse ? "1" : "0"), FALSE);
		generateGrayCode(nBits - 1, Concat(str, reverse ? "0" : "1"), TRUE);
	}
}